/*----------------------------------------------------------------------*
 *	CLASS:		Qt3Step
 *	Quantum Tic Tac Toe
 *	Copyright (c) 2004-2009 Novatia Labs, Inc.  All rights reserved.
 *----------------------------------------------------------------------*/

package com.novatialabs.qttt.engine.impl;

import com.novatialabs.qttt.engine.Qt3Player;

/**
 * Step keeps track of a step in a Quantum Tic Tac Toe game.
 *
 * @Author	John Levine
 * @Author	Duane Gibson
 * @Author Friendly development resources cheerfully provided by Charles Phares.
 * @Author	$Author$
 * @Version	$Revision$
 */

/*package*/ abstract class Qt3Step
{

   /**
    * The move number (in the range 1 to 9).
    */
    private final int		moveNumber;	// 1 to 9.

   /**
    * The step before this one.
    */
    private final Qt3Step	previousStep;

   /**
    * The state of the game, evaluated after this step is completed.
    */
    private Qt3State		evaluatedState;


   /*-------------------------------------------------------------------*
    *	CONSTRUCTOR:	Qt3Step()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Sat Jun 19 17:33:42 PDT 2004
    *-------------------------------------------------------------------*/
   /**
    * Disabled zero-arg constructor.
    */

    protected Qt3Step()
    {
	throw new IllegalStateException();
    } // Qt3Step()

   /*-------------------------------------------------------------------*
    *	CONSTRUCTOR:	Qt3Step()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Sat Jun 19 17:33:50 PDT 2004
    *-------------------------------------------------------------------*/
   /**
    * Constructs a step.
    */

    /*package*/ Qt3Step(
	int		moveNum,
	Qt3Step		prevStep
	)
    {

	this.moveNumber = moveNum;
	this.previousStep = prevStep;

	this.clear();

    } // Qt3Step()

   /*-------------------------------------------------------------------*
    *	METHOD:		clear()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Sat Mar  6 14:19:17 PST 2004
    *-------------------------------------------------------------------*/
   /**
    * Clears this move object to an initial state.
    */

    /*package*/ final void clear()
    {
	this.evaluatedState = null;
	this.clearStep();
    } // clear()

   /*-------------------------------------------------------------------*
    *	METHOD:		clearStep()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Mon Jan  3 22:17:35 PST 2005
    *-------------------------------------------------------------------*/
   /**
    * To be implemented by subclasses to clear their state.
    */

    protected abstract void clearStep() ;


   /*-------------------------------------------------------------------*
    *	METHOD:		getMoveNumber()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Sat Mar  6 14:10:36 PST 2004
    *-------------------------------------------------------------------*/
   /**
    * Returns number of this move (in the range 1 to 9).
    */

    public int getMoveNumber() {
	return this.moveNumber;
    } // getMoveNumber()

   /*-------------------------------------------------------------------*
    *	METHOD:		getPreviousStep()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Wed Jan  5 22:48:02 PST 2005
    *-------------------------------------------------------------------*/
   /**
    * Returns the step that comes before this one.
    */

    public final Qt3Step getPreviousStep()
    {
	return this.previousStep;
    } // getPreviousStep()


   /*-------------------------------------------------------------------*
    *	METHOD:		isRedoable()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Sat Jun  5 16:43:01 PDT 2004
    *-------------------------------------------------------------------*/
   /**
    * Returns whether this step can be "redone" (because it holds previous
    * input).
    */

    /*package*/ abstract boolean isRedoable();


   /*-------------------------------------------------------------------*
    *	METHOD:		isAutomatic()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Sat Jun 19 17:39:14 PDT 2004
    *-------------------------------------------------------------------*/
   /**
    * Returns whether this step is "automatic".
    * This means that no user input is required, the completion of the step
    * is automatically implied by the state of the game.
    * Note if a step is automatic, it is assumed to also be redo-able.
    */

    /*package*/ abstract boolean isAutomatic();

   /*-------------------------------------------------------------------*
    *	METHOD:		getPlayer()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Mon Jan  3 20:18:55 PST 2005
    *-------------------------------------------------------------------*/
   /**
    * Returns the player who performs this step.
    */

    public abstract Qt3Player getPlayer();

   /*-------------------------------------------------------------------*
    *	METHOD:		evaluateState()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Wed Jan  5 23:34:33 PST 2005
    *-------------------------------------------------------------------*/
   /**
    * Evaluates this state of this step from the state of the previous
    * step and the changes made in this step.
    */

    public final void evaluateState()
    {
	Qt3State prevState;
	final Qt3Step prevStep = this.previousStep;
	if ( prevStep == null ) {
	    prevState = new Qt3State();
	} else {
	    prevState = prevStep.getState();
	    prevState.isGameOver();// assert(prevState != null); by calling a simple method
	}
	this.evaluatedState = this.transformState(prevState);
	this.evaluatedState.isGameOver();// assert(this.evaluatedState != null); by calling a simple method
    } // evaluateState()

   /*-------------------------------------------------------------------*
    *	METHOD:		transformState()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Wed Jan  5 23:54:19 PST 2005
    *-------------------------------------------------------------------*/
   /**
    * Returns a state object that consists of the given state modified by
    * the changes introduced by this step.
    */

    protected abstract Qt3State transformState(
	Qt3State	prevState
	);

   /*-------------------------------------------------------------------*
    *	METHOD:		getState()
    *	AUTHOR:		Duane Gibson
    *	CREATION DATE:	Mon Jan  3 22:28:32 PST 2005
    *-------------------------------------------------------------------*/
   /**
    * Returns the evaluted state of this step, if any.
    */

    public final Qt3State getState()
    {
	return this.evaluatedState;
    } // getState()

} // class Qt3Step

